﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Brio.Framework
{
    // Needs access to the technique collection
    public class Technique
    {

        // just read in stuff, worry about a formal process later
        // BETA CONSTRUCTOR WHICH WILL BE USED FOR EXACTLY WHAT IM TESTING FOR, THIS NEEDS TO BE MADE GENERIC
        public Technique(string rhythmString, string notesString,
                        string name, double value, string neighbor, double neighborMultiplier, double decayRate,
                        RhythmTechniqueType rhythmType, NoteTechniqueType noteType, NoteTechniqueFormat noteFormat)
        {
            if (noteFormat == NoteTechniqueFormat.MIDINoteValue)
            {
                System.Windows.Forms.MessageBox.Show("Currently not supported, sorry! Please use Scientific Note Format");
                return;
            }

            this.value = value;
            this.neighborMultiplier = neighborMultiplier;
            this.neighbor = neighbor;
            this.decayRate = decayRate;
            this.name = name;
            this.rhythmType = rhythmType;
            this.noteType = noteType;
            this.noteFormat = noteFormat;

            ///////////////////////////////////////
            // Read in Rhythm Array              //
            ///////////////////////////////////////

            // Read in rhythms in my notation format, really easy
            rhythm = new List<int>();

            string[] rhythmArray = rhythmString.Split(new char[] { ' ' });

            int rLength = 0;

            foreach (string rNotated in rhythmArray)
            {
                Tuple<int, bool> rEntry = Note.RhythmTable[rNotated];

                rLength += rEntry.Item1; // Add note length value

                // New Note
                if (rEntry.Item2 == false)
                {
                    rhythm.Add(rLength);
                    rLength = 0;
                }
                // Hold of previous note
                else { }

            }

            ///////////////////////////////////////
            // Read in Note Array              //
            ///////////////////////////////////////


            notes = new List<Note>();

            string[] notesArray = notesString.Split(new char[] { ' ' });

            foreach (string scientificNote in notesArray)
            {
                // TODO: Allow them to read in just raw note values.
                // Read in my note values in scientific notation
                int noteValue = Note.NoteTable[scientificNote];

                // TODO: Add Rest notes
                notes.Add(new Note(Framework.NoteType.Note, noteValue));
            }


            ///////////////////////////////////////
            // Calculate Technique Length        //
            ///////////////////////////////////////

            int divFactor = Constants.RHYTHM_WHOLE_VALUE / Constants.SMALLEST_RHYTHMIC_UNIT;

            // Pre-injection boundary check
            int rhythmSum = 0;

            for (int i = 0; i < Rhythm.Count; i++)
            {
                rhythmSum += Rhythm[i] / divFactor;
            }

            length = rhythmSum;

            ///////////////////////////////////////
            // Calculate Interval Array          //
            ///////////////////////////////////////



        }



        // TODO : XML Constructor
        public Technique(string fileName)
        {
        }

        /* This encodes an arpegio didy that I like
         * 
         * <Technique>
         *      <Notes Format="Scientific Notation" Type="Interval">
         *          C4 E4 G4 C5 G4 E4 C4
         *      </Notes>
         *      <Rhythm Format="Musical Notation" Type=">
         *          Eighth Eighth Eighth Eighth Eighth Eighth Quarter
         *      </Rhythm>
         * <Technique>
         */

        private List<Note> notes;
        private List<int> intervals;
        private List<int> rhythm;

        private string name;
        private double value;
        private string neighbor;
        private double neighborMultiplier;
        private double decayRate;
        private int length;

        private RhythmTechniqueType rhythmType;
        private NoteTechniqueType noteType;
        private NoteTechniqueFormat noteFormat;


        public List<Note> Notes
        {
            get { return notes; }
        }

        public List<int> Intervals
        {
            get { return intervals; }
        }

        public List<int> Rhythm
        {
            get { return rhythm; }
        }

        public int Length
        {
            get { return length; }
        }

        public double Value
        {
            get { return value; }
            set { this.value = value; }
        }

        public double NeighborMultiplier
        {
            get { return neighborMultiplier; }
            set { neighborMultiplier = value;}
        }

        public double DecayRate
        {
            get { return decayRate; }
            set { decayRate = value; }
        }

        public string Name
        {
            get { return name; }
        }
        public string Neighbor
        {
            get { return neighbor; }
            set { neighbor = value; }
        }

        public RhythmTechniqueType RhythmType
        {
           get { return rhythmType; }
        }

        public NoteTechniqueType NoteType
        {
            get { return noteType; }
        }

        public NoteTechniqueFormat NoteFormat
        {
            get { return noteFormat;}
        }
 


    }

    public enum RhythmTechniqueType
    {
        RhythmRelationship, None
    }

    public enum NoteTechniqueType
    {
        IntervalRelationship, NoteRelationship, None
    }

    public enum NoteTechniqueFormat
    {
        ScientificNotation, MIDINoteValue
    }


}
